package io.github.yezhihao.cipher;

import javax.xml.bind.DatatypeConverter;
import java.security.InvalidKeyException;
import java.security.KeyPair;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.util.Scanner;

/**
 * ECDSA-secp256k1 签名工具
 */
public class Application {

    public static void main(String[] args) {
        final Scanner scanner = new Scanner(System.in);
        String help = "-------------------------------------------\n" +
                "生成密钥 -k \n" +
                "生成签名 -s {私钥} {数据}\n" +
                "验证签名 -v {公钥} {数据} {签名}\n" +
                "退出 -e\n" +
                "-------------------------------------------\n";
        System.out.print(help);
        while (true) {
            String cmd = scanner.nextLine();
            if (cmd == null || cmd.isEmpty())
                continue;
            if (cmd.startsWith("-k")) {
                KeyPair keyPair = ECDSAUtils.createKeyPair();
                byte[] publicKey = keyPair.getPublic().getEncoded();
                byte[] privateKey = keyPair.getPrivate().getEncoded();
                System.out.println("pub: " + DatatypeConverter.printHexBinary(publicKey).substring(48));
                System.out.println("pri: " + DatatypeConverter.printHexBinary(privateKey).substring(64));

            } else if (cmd.startsWith("-s")) {
                String[] cmds = cmd.split(" ");

                PrivateKey privateKey;
                try {
                    String pri_str = cmds[1];
                    privateKey = ECDSAUtils.getPrivateKey(pri_str);
                } catch (InvalidKeyException e) {
                    System.out.println("私钥格式错误");
                    continue;
                }

                byte[] data;
                try {
                    String data_str = cmds[2];
                    data = DatatypeConverter.parseHexBinary(data_str);
                } catch (Exception e) {
                    System.out.println("数据格式错误，应为十六进制字符串");
                    continue;
                }

                byte[] sign;
                try {
                    sign = ECDSAUtils.sign(privateKey, data);
                    sign = ECDSAUtils.removeSpecInfo(sign);
                    System.out.println("sig: " + DatatypeConverter.printHexBinary(sign));
                } catch (Exception e) {
                    System.out.println("签名失败: " + e.getMessage());
                    continue;
                }

            } else if (cmd.startsWith("-v")) {
                String[] cmds = cmd.split(" ");
                String sig_str = cmds[3];

                PublicKey publicKey;
                try {
                    String pub_str = cmds[1];
                    publicKey = ECDSAUtils.getPublicKey(pub_str);
                } catch (InvalidKeyException e) {
                    System.out.println("公钥格式错误");
                    continue;
                }

                byte[] data;
                try {
                    String data_str = cmds[2];
                    data = DatatypeConverter.parseHexBinary(data_str);
                } catch (Exception e) {
                    System.out.println("数据格式错误，应为十六进制字符串");
                    continue;
                }
                byte[] sig;
                try {
                    sig = DatatypeConverter.parseHexBinary(sig_str);
                    sig = ECDSAUtils.addSpecInfo(sig);
                    boolean verify = ECDSAUtils.verify(publicKey, data, sig);
                    System.out.println("result: " + verify);
                } catch (Exception e) {
                    System.out.println("签名格式错误");
                    continue;
                }
            } else if (cmd.startsWith("-e")) {
                return;
            } else {
                System.out.println(help);
            }
            System.out.println();
        }
    }
}